package ctrl_cali

import (
	"encoding/json"
	"errors"
	"github.com/wsw188440873/ctrl-cali/hub"
	"github.com/wsw188440873/ctrl-cali/sailhero"
	types "github.com/wsw188440873/ctrl-cali/types"
	caliType "iot-base/common/types"
	"strconv"
	"time"
)

func ZeroCaliAction(params []byte) ([]byte, error) {
	req := caliType.ReqZeroCali{}
	err := json.Unmarshal(params, &req)
	if err != nil {
		return []byte{}, err
	}
	cali, err := NewCali("sailhero", req.StationId, req.ThingId, req.CaliId, req.ModelId, req.RequestId)
	if err != nil {
		return []byte{}, err
	}
	err = cali.ZeroCali(types.ZeroCali{
		Event: req.Event,
		From:  "cloud",
	})
	return []byte{}, err
}

func SpanCaliAction(params []byte) ([]byte, error) {
	req := caliType.ReqSpanCali{}
	err := json.Unmarshal(params, &req)
	if err != nil {
		return []byte{}, err
	}
	cali, err := NewCali("sailhero", req.StationId, req.ThingId, req.CaliId, req.ModelId, req.RequestId)
	if err != nil {
		return []byte{}, err
	}
	err = cali.SpanCali(types.SpanCali{
		Event:  req.Event,
		Number: req.Number,
		Units:  req.Units,
		From:   "cloud",
	})
	return []byte{}, err
}

func CaliTasktAction(params []byte) ([]byte, error) {
	var req caliType.ReqCaliTask
	err := json.Unmarshal(params, &req)
	if err != nil {
		return []byte{}, err
	}
	cali, err := NewCali("sailhero", req.StationId, req.ThingId, req.CaliId, req.ModelId, req.RequestId)
	if err != nil {
		return []byte{}, err
	}
	//检查是否有任务正在执行.
	isRun := cali.IsRunTask()
	if isRun == true {
		return []byte{}, errors.New("错误操作,其他任务正在运行")
	}
	//执行校准任务
	taskId, err := cali.CaliTask("", req.TaskType, "自动测试", "manual", types.GroupTask{})
	if err != nil {
		return []byte{}, err
	}
	resp := map[string]string{
		"task_id": taskId,
	}
	b, _ := json.Marshal(resp)
	return b, nil
}

type ReqZeroOrSpanStatus struct {
	StationId string `json:"station_id"`
}

func GetZeroOrSpanStatus(params []byte) ([]byte, error) {
	var dataMap ReqZeroOrSpanStatus
	err := json.Unmarshal(params, &dataMap)
	if err != nil {
		return []byte{}, err
	}
	caliData := sailhero.CaliObj.GetStatis(dataMap.StationId)
	result := map[string]string{
		"model_id": caliData.ModelId,
		"type":     caliData.Type,
		"event":    caliData.Event,
	}
	b, _ := json.Marshal(result)
	return b, nil
}

func ResetZeroOrSpanStatus(params []byte) ([]byte, error) {
	var dataMap ReqZeroOrSpanStatus
	err := json.Unmarshal(params, &dataMap)
	if err != nil {
		return []byte{}, err
	}
	caliData := sailhero.CaliObj.GetStatis(dataMap.StationId)
	if caliData.ModelId == "" {
		return nil, nil
	}
	switch caliData.Type {
	case "zero":
		if caliData.Params != nil {
			if _, ok := caliData.Params.(types.ZeroCali); ok {
				caliTask, _ := NewCali("sailhero", dataMap.StationId, caliData.ThingId, caliData.CaliId, caliData.ModelId, strconv.FormatInt(time.Now().Unix(), 10))
				caliTask.ZeroCali(types.ZeroCali{
					Event: types.End,
				})
			}
		}
		break
	case "span":
		if caliData.Params != nil {
			if data, ok := caliData.Params.(types.SpanCali); ok {
				caliTask, _ := NewCali("sailhero", dataMap.StationId, caliData.ThingId, caliData.CaliId, caliData.ModelId, strconv.FormatInt(time.Now().Unix(), 10))
				caliTask.SpanCali(types.SpanCali{
					Event:  types.End,
					Number: data.Number,
					Units:  data.Units,
				})
			}
		}
		break
	}
	return nil, nil
}

func StopCaliTask(bytes []byte) ([]byte, error) {
	// 停止现在正在运行的任务
	hub.TaskManager.Stop()
	// 重新初始化參數.
	hub.TaskManager.RestParams()
	return nil, nil
}

func QueryRunTask(bytes []byte) ([]byte, error) {
	params := hub.TaskManager.GetTaskParams()
	var modelId string
	if value, ok := params["model_id"]; ok {
		modelId = value.(string)
	}
	var taskType string
	if value, ok := params["task_type"]; ok {
		taskType = value.(string)
	}
	var value string
	if v, ok := params["value"]; ok {
		value = v.(string)
	}
	var status int
	if v, ok := params["code"]; ok {
		status = v.(int)
	}
	var currTask int
	if v, ok := params["curr"]; ok {
		currTask = v.(int)
	}
	var totalTask int
	if v, ok := params["total"]; ok {
		totalTask = v.(int)
	}
	var taskId string
	if v, ok := params["task_id"]; ok {
		taskId = v.(string)
	}
	result := map[string]any{
		"task_id":    taskId,
		"model_id":   modelId,
		"task_type":  taskType,
		"curr_task":  currTask,
		"total_task": totalTask,
		"value":      value,
		"status":     status,
	}
	return json.Marshal(result)
}
